# asterisk-dialplan.pm
# Copyright (C) 2006,2007  Stephane Alnet
#
# This program is free software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 3
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program.  If not, see <http://www.gnu.org/licenses/>.
# 

#
# For more information: http://carrierclass.net/
#
package CCNv2::Provision::Asterisk::dialplan;
use strict;
use warnings;
use base qw(CCNCore::Provision::Base);
use CCN::Text;
use CCNCore::Scripting;

# asterisk_dialplan()
#   Generate the generic Asterisk dialplan for an enterprise entry.
#
#   Especially provides the 'errors' and 'services' routes.
#   In the 'services' route, 'vm-login', 'vm-password', 'vm-no-password', 
#   'cfa-set', 'cfa-del', 'dnd-set', 'dnd-del' are provided to build
#   more advance menus or groups.

sub run()
{
    my $self = shift;
    return unless defined $self->p->{cp_cluster};

    my $SOUNDS = $self->p->{sounds};
    $self->CHECKFOR("$SOUNDS/call-fwd-unconditional.gsm");
    $self->CHECKFOR("$SOUNDS/silence/1.gsm");
    $self->CHECKFOR("$SOUNDS/pls-ent-num-transfer.gsm");

    $self->sql_do_for(<<'SQL', $self->p->{cp_cluster},
        SELECT pk, length FROM enterprise
        WHERE pk IN (SELECT DISTINCT enterprise FROM pool WHERE cp_cluster = ?)
SQL
    sub
    {
        my $ENTERPRISE  = shift;
        my $EXTLEN      = shift;

        my $EXT    = 'X' x ${EXTLEN};

        IF_CHANGED '' => "mkdir -p /etc/asterisk/config/clients/${ENTERPRISE}";
        IF_CHANGED '' => "mkdir -p ${SOUNDS}/prompts/${ENTERPRISE}";
        IF_CHANGED '' => "chown asterisk ${SOUNDS}/prompts/${ENTERPRISE}";

        # TBD Need to evaluate this in a given CoS. (Remember CoS are also ACLs, right?)
        # -> this is the same problem as figuring out the dialing digitmap for a phone.
        # (For now we use ${EXT} as the pattern, but this may result in invalid forwarding patterns
        # been set up.)
        my $cfa_tui = <<"EOT";
[${ENTERPRISE}-set-cfa-tui] ; extension, context, destcontext
exten => s,1,Answer(2)
exten => s,n,Background(call-fwd-unconditional\&pls-ent-num-transfer)
exten => s,n,ResponseTimeout(10)
exten => s,n,WaitExten(8)
exten => s,n,Background(silence/1)
exten => s,n,Background(pls-try-again)
exten => s,n,Goto(s,2)
exten => i,1,Goto(s,2)
exten => t,1,Goto(s,2)
;
; Internal CFA
exten => _${EXT},1,Macro(set-cfa,\${CALLERID(num)},\${ENTERPRISE},\${EXTEN}\@${ENTERPRISE}-ring)
exten => _${EXT},2,Hangup
;
EOT

        foreach("/etc/asterisk/config/clients/${ENTERPRISE}/extensions.main.conf")
        {
            CAT $_, copyright(';').<<"EOT".$cfa_tui;
;
[${ENTERPRISE}-services]
;
; TBD include => ${ENTERPRISE}-parkedcalls
;
exten => vm-no-password,1,Goto(${ENTERPRISE}-\${EXTEN},s,1)
exten => vm-password,1,Goto(${ENTERPRISE}-\${EXTEN},s,1)
exten => vm-login,1,Goto(${ENTERPRISE}-\${EXTEN},s,1)
;
exten => cfa-set,1,Goto(${ENTERPRISE}-\${EXTEN},s,1)
exten => cfa-del,1,Goto(${ENTERPRISE}-\${EXTEN},s,1)
exten => dnd-set,1,Goto(${ENTERPRISE}-\${EXTEN},s,1)
exten => dnd-del,1,Goto(${ENTERPRISE}-\${EXTEN},s,1)
;
; TBD Figure a way to actually be able to define operator in "enterprise"
exten => 0,1,Goto(\${POOL}-operator,s,1)
exten => o,1,Goto(\${POOL}-operator,s,1)
;
[${ENTERPRISE}-cfa-set]
exten => s,1,Goto(${ENTERPRISE}-set-cfa-tui,s,1)
[${ENTERPRISE}-cfa-del]
exten => s,1,Macro(del-cfa,\${CALLERID(num)},${ENTERPRISE})
[${ENTERPRISE}-dnd-set]
exten => s,1,Macro(set-dnd,\${CALLERID(num)},${ENTERPRISE})
[${ENTERPRISE}-dnd-del]
exten => s,1,Macro(del-dnd,\${CALLERID(num)},${ENTERPRISE})

[${ENTERPRISE}-vm-login]
exten => s,1,Answer(1)
exten => s,2,Background(vm-login)
exten => ${EXT},1,Macro(dispatch,VMm${ENTERPRISE}m\${EXTEN})
exten => i,1,Goto(s,2)
exten => t,1,Goto(s,2)
;
[${ENTERPRISE}-vm-no-password]
exten => s,1,Macro(dispatch,VMs${ENTERPRISE}m\${CALLERID(num)})
;
[${ENTERPRISE}-vm-password]
exten => s,1,Macro(dispatch,VMm${ENTERPRISE}m\${CALLERID(num)})
;
[${ENTERPRISE}-errors]
exten => i,1,answer
exten => i,n,wait(1)
exten => i,n,playback(pbx-invalid)
exten => i,n,wait(1)
exten => i,n,playback(goodbye)
exten => i,n,hangup
;
exten => t,1,answer
exten => t,n,wait(1)
exten => t,n,playback(goodbye)
exten => t,n,hangup()
;
exten => h,1,noop(End of call: UID=\${UNIQUEID} CID=\${CALLERID} Disconnect=\${HANGUPCAUSE} Start=\${DIALTIME} End=\${DATETIME})
exten => h,2,hangup()
;
[macro-${ENTERPRISE}-set-context]
exten => s,1,Set(SOUNDS=${SOUNDS})
;
EOT

            IF_CHANGED $_ => CCNv2::Scripting::AST('extensions reload');
        } # extensions.main.conf
    }); # foreach @cp_enterprises

}
1;